<template>
  <el-dialog
    v-model="dialogVisible"
    :title="dialogTitle"
    width="1000px"
    :close-on-click-modal="false"
    :close-on-press-escape="false"
    @close="handleClose"
  >
    <div class="permission-dialog">
      <!-- 搜索和过滤 -->
      <div class="permission-header">
        <el-row :gutter="20" class="search-row">
          <el-col :span="8">
            <el-input
              v-model="searchKeyword"
              :placeholder="$t('PermissionManagement.SearchPermission')"
              clearable
              @input="handleSearch"
            >
              <template #prefix>
                <el-icon><Search /></el-icon>
              </template>
            </el-input>
          </el-col>
          <el-col :span="6">
            <el-select
              v-model="selectedGroup"
              :placeholder="$t('PermissionManagement.SelectGroup')"
              clearable
              @change="handleGroupChange"
            >
              <el-option
                v-for="group in permissionGroups"
                :key="group.name"
                :label="group.displayName"
                :value="group.name"
              />
            </el-select>
          </el-col>
          <el-col :span="6">
            <el-select
              v-model="filterType"
              :placeholder="$t('PermissionManagement.FilterType')"
              @change="handleFilterChange"
            >
              <el-option
                :label="$t('PermissionManagement.AllPermissions')"
                value="all"
              />
              <el-option
                :label="$t('PermissionManagement.GrantedPermissions')"
                value="granted"
              />
              <el-option
                :label="$t('PermissionManagement.DeniedPermissions')"
                value="denied"
              />
            </el-select>
          </el-col>
          <el-col :span="4">
            <el-button type="primary" @click="expandAll">
              {{ $t('PermissionManagement.ExpandAll') }}
            </el-button>
          </el-col>
        </el-row>
      </div>

      <!-- 权限树 -->
      <div class="permission-tree-container">
        <el-tree
          ref="permissionTreeRef"
          :data="filteredPermissions"
          :props="{ children: 'children', label: 'displayName' }"
          show-checkbox
          node-key="name"
          :default-checked-keys="grantedPermissions"
          :default-expanded-keys="expandedKeys"
          :filter-node-method="filterNode"
          @check="handlePermissionCheck"
          @node-expand="handleNodeExpand"
          @node-collapse="handleNodeCollapse"
        >
          <template #default="{ node, data }">
            <div class="permission-node">
              <div class="permission-info">
                <div class="permission-name">
                  {{ data.displayName }}
                  <el-tag v-if="data.isGranted" type="success" size="small">
                    {{ $t('PermissionManagement.Granted') }}
                  </el-tag>
                </div>
                <div class="permission-description">{{ data.description }}</div>
                <div class="permission-meta">
                  <span class="permission-group">{{ data.groupName }}</span>
                  <span v-if="data.parentName" class="permission-parent">
                    {{ $t('PermissionManagement.Parent') }}: {{ data.parentName }}
                  </span>
                </div>
              </div>
              <div class="permission-actions">
                <el-switch
                  v-model="data.isGranted"
                  :disabled="data.isStatic || !canManage"
                  @change="handlePermissionToggle(data)"
                />
              </div>
            </div>
          </template>
        </el-tree>
      </div>

      <!-- 统计信息 -->
      <div class="permission-stats">
        <el-row :gutter="20">
          <el-col :span="6">
            <el-statistic :title="$t('PermissionManagement.TotalPermissions')" :value="totalPermissions" />
          </el-col>
          <el-col :span="6">
            <el-statistic :title="$t('PermissionManagement.GrantedCount')" :value="grantedCount">
              <template #suffix>
                <span class="stat-percentage">({{ grantedPercentage }}%)</span>
              </template>
            </el-statistic>
          </el-col>
          <el-col :span="6">
            <el-statistic :title="$t('PermissionManagement.DeniedCount')" :value="deniedCount">
              <template #suffix>
                <span class="stat-percentage">({{ deniedPercentage }}%)</span>
              </template>
            </el-statistic>
          </el-col>
          <el-col :span="6">
            <el-statistic :title="$t('PermissionManagement.StaticPermissions')" :value="staticCount" />
          </el-col>
        </el-row>
      </div>

      <!-- 批量操作 -->
      <div class="permission-bulk-actions">
        <el-space>
          <el-button
            :disabled="!canManage || selectedPermissions.length === 0"
            @click="grantSelected"
          >
            <el-icon><Check /></el-icon>
            {{ $t('PermissionManagement.GrantSelected') }}
          </el-button>
          <el-button
            :disabled="!canManage || selectedPermissions.length === 0"
            @click="revokeSelected"
          >
            <el-icon><Close /></el-icon>
            {{ $t('PermissionManagement.RevokeSelected') }}
          </el-button>
          <el-button
            :disabled="!canManage"
            @click="grantAll"
          >
            {{ $t('PermissionManagement.GrantAll') }}
          </el-button>
          <el-button
            :disabled="!canManage"
            @click="revokeAll"
          >
            {{ $t('PermissionManagement.RevokeAll') }}
          </el-button>
          <el-button
            :disabled="!canManage"
            @click="resetToDefault"
          >
            {{ $t('PermissionManagement.ResetToDefault') }}
          </el-button>
        </el-space>
      </div>
    </div>

    <template #footer>
      <div class="dialog-footer">
        <el-button @click="handleClose">{{ $t('Common.Cancel') }}</el-button>
        <el-button type="primary" :loading="loading" @click="handleSubmit">
          {{ $t('Common.Save') }}
        </el-button>
      </div>
    </template>
  </el-dialog>
</template>

<script setup lang="ts">
import { ref, reactive, computed, watch, nextTick } from 'vue'
import { ElMessage, ElMessageBox, ElTree } from 'element-plus'
import { Search, Check, Close } from '@element-plus/icons-vue'
import { permissionService } from '@/services/permission.service'
import { abpService } from '@/services/abp.service'
import type { Permission, PermissionGroup } from '@/types/abp'

interface Props {
  modelValue: boolean
  entityType?: 'user' | 'role' | 'tenant'
  entityId?: string
  entityName?: string
  readOnly?: boolean
}

interface Emits {
  (e: 'update:modelValue', value: boolean): void
  (e: 'success'): void
}

const props = withDefaults(defineProps<Props>(), {
  readOnly: false
})

const emit = defineEmits<Emits>()

const permissionTreeRef = ref<InstanceType<typeof ElTree>>()
const loading = ref(false)
const searchKeyword = ref('')
const selectedGroup = ref('')
const filterType = ref('all')
const expandedKeys = ref<string[]>([])
const selectedPermissions = ref<string[]>([])

const dialogVisible = computed({
  get: () => props.modelValue,
  set: (value) => emit('update:modelValue', value)
})

const canManage = computed(() => {
  if (props.readOnly) return false

  switch (props.entityType) {
    case 'user':
      return abpService.hasPermission('Identity.Users.ManagePermissions')
    case 'role':
      return abpService.hasPermission('Identity.Roles.ManagePermissions')
    case 'tenant':
      return abpService.hasPermission('TenantManagement.Tenants.ManagePermissions')
    default:
      return false
  }
})

const dialogTitle = computed(() => {
  const typeMap = {
    user: $t('PermissionManagement.UserPermissions'),
    role: $t('PermissionManagement.RolePermissions'),
    tenant: $t('PermissionManagement.TenantPermissions')
  }
  const baseTitle = typeMap[props.entityType!] || $t('PermissionManagement.ManagePermissions')
  return props.entityName ? `${baseTitle} - ${props.entityName}` : baseTitle
})

// 权限数据
const permissions = ref<Permission[]>([])
const permissionGroups = ref<PermissionGroup[]>([])
const originalPermissions = ref<Permission[]>([])
const grantedPermissions = ref<string[]>([])

// 过滤后的权限
const filteredPermissions = computed(() => {
  let filtered = [...permissions.value]

  // 按组过滤
  if (selectedGroup.value) {
    filtered = filtered.filter(p => p.groupName === selectedGroup.value)
  }

  // 按授权状态过滤
  if (filterType.value === 'granted') {
    filtered = filtered.filter(p => p.isGranted)
  } else if (filterType.value === 'denied') {
    filtered = filtered.filter(p => !p.isGranted)
  }

  return buildPermissionTree(filtered)
})

// 统计信息
const totalPermissions = computed(() => permissions.value.length)
const grantedCount = computed(() => permissions.value.filter(p => p.isGranted).length)
const deniedCount = computed(() => permissions.value.filter(p => !p.isGranted).length)
const staticCount = computed(() => permissions.value.filter(p => p.isStatic).length)
const grantedPercentage = computed(() => {
  if (totalPermissions.value === 0) return 0
  return Math.round((grantedCount.value / totalPermissions.value) * 100)
})
const deniedPercentage = computed(() => {
  if (totalPermissions.value === 0) return 0
  return Math.round((deniedCount.value / totalPermissions.value) * 100)
})

// 构建权限树
const buildPermissionTree = (flatPermissions: Permission[]) => {
  const tree: Permission[] = []
  const nodeMap = new Map<string, Permission>()

  // 创建所有节点
  flatPermissions.forEach(permission => {
    nodeMap.set(permission.name, { ...permission })
  })

  // 构建树形结构
  flatPermissions.forEach(permission => {
    const node = nodeMap.get(permission.name)!
    if (!permission.parentName || !nodeMap.has(permission.parentName)) {
      tree.push(node)
    } else {
      const parent = nodeMap.get(permission.parentName)!
      if (!parent.children) {
        parent.children = []
      }
      parent.children.push(node)
    }
  })

  return tree
}

// 加载权限数据
const loadPermissions = async () => {
  if (!props.entityId || !props.entityType) return

  try {
    loading.value = true

    let result
    switch (props.entityType) {
      case 'user':
        result = await permissionService.getUserPermissions(props.entityId)
        break
      case 'role':
        result = await permissionService.getRolePermissions(props.entityId)
        break
      case 'tenant':
        result = await permissionService.getTenantPermissions(props.entityId)
        break
      default:
        throw new Error('不支持的实体类型')
    }

    permissions.value = result.permissions
    originalPermissions.value = JSON.parse(JSON.stringify(result.permissions))
    grantedPermissions.value = result.permissions
      .filter(p => p.isGranted)
      .map(p => p.name)

    // 加载权限组
    const groupsResult = await permissionService.getPermissionGroups()
    permissionGroups.value = groupsResult

    // 默认展开所有根节点
    expandedKeys.value = result.permissions
      .filter(p => !p.parentName)
      .map(p => p.name)
  } catch (error) {
    console.error('加载权限失败:', error)
    ElMessage.error($t('PermissionManagement.LoadPermissionsFailed'))
  } finally {
    loading.value = false
  }
}

// 搜索处理
const handleSearch = () => {
  permissionTreeRef.value?.filter(searchKeyword.value)
}

// 过滤节点
const filterNode = (value: string, data: Permission) => {
  if (!value) return true
  return data.displayName.toLowerCase().includes(value.toLowerCase()) ||
         data.name.toLowerCase().includes(value.toLowerCase()) ||
         data.description?.toLowerCase().includes(value.toLowerCase())
}

// 组过滤处理
const handleGroupChange = () => {
  // 重新构建树形结构
  nextTick(() => {
    permissionTreeRef.value?.filter(searchKeyword.value)
  })
}

// 类型过滤处理
const handleFilterChange = () => {
  // 重新构建树形结构
  nextTick(() => {
    permissionTreeRef.value?.filter(searchKeyword.value)
  })
}

// 权限选择处理
const handlePermissionCheck = (data: any, checked: any) => {
  selectedPermissions.value = checked.checkedKeys
}

// 节点展开处理
const handleNodeExpand = (data: Permission) => {
  if (!expandedKeys.value.includes(data.name)) {
    expandedKeys.value.push(data.name)
  }
}

// 节点折叠处理
const handleNodeCollapse = (data: Permission) => {
  const index = expandedKeys.value.indexOf(data.name)
  if (index > -1) {
    expandedKeys.value.splice(index, 1)
  }
}

// 权限切换处理
const handlePermissionToggle = (permission: Permission) => {
  if (permission.isStatic) return

  // 更新子权限状态
  const updateChildren = (parent: Permission) => {
    if (parent.children) {
      parent.children.forEach(child => {
        if (!child.isStatic) {
          child.isGranted = parent.isGranted
          updateChildren(child)
        }
      })
    }
  }

  updateChildren(permission)
}

// 展开所有节点
const expandAll = () => {
  const allKeys = permissions.value.map(p => p.name)
  expandedKeys.value = allKeys
  nextTick(() => {
    permissionTreeRef.value?.setExpandedKeys(allKeys)
  })
}

// 授权选中的权限
const grantSelected = () => {
  selectedPermissions.value.forEach(permissionName => {
    const permission = permissions.value.find(p => p.name === permissionName)
    if (permission && !permission.isStatic) {
      permission.isGranted = true
      handlePermissionToggle(permission)
    }
  })
  ElMessage.success($t('PermissionManagement.GrantSelectedSuccess'))
}

// 撤销选中的权限
const revokeSelected = () => {
  selectedPermissions.value.forEach(permissionName => {
    const permission = permissions.value.find(p => p.name === permissionName)
    if (permission && !permission.isStatic) {
      permission.isGranted = false
      handlePermissionToggle(permission)
    }
  })
  ElMessage.success($t('PermissionManagement.RevokeSelectedSuccess'))
}

// 授权所有权限
const grantAll = async () => {
  try {
    await ElMessageBox.confirm(
      $t('PermissionManagement.GrantAllConfirm'),
      $t('PermissionManagement.GrantAll'),
      {
        confirmButtonText: $t('Common.Confirm'),
        cancelButtonText: $t('Common.Cancel'),
        type: 'warning'
      }
    )

    permissions.value.forEach(permission => {
      if (!permission.isStatic) {
        permission.isGranted = true
      }
    })

    ElMessage.success($t('PermissionManagement.GrantAllSuccess'))
  } catch (error) {
    // 用户取消
  }
}

// 撤销所有权限
const revokeAll = async () => {
  try {
    await ElMessageBox.confirm(
      $t('PermissionManagement.RevokeAllConfirm'),
      $t('PermissionManagement.RevokeAll'),
      {
        confirmButtonText: $t('Common.Confirm'),
        cancelButtonText: $t('Common.Cancel'),
        type: 'warning'
      }
    )

    permissions.value.forEach(permission => {
      if (!permission.isStatic) {
        permission.isGranted = false
      }
    })

    ElMessage.success($t('PermissionManagement.RevokeAllSuccess'))
  } catch (error) {
    // 用户取消
  }
}

// 重置为默认
const resetToDefault = async () => {
  try {
    await ElMessageBox.confirm(
      $t('PermissionManagement.ResetToDefaultConfirm'),
      $t('PermissionManagement.ResetToDefault'),
      {
        confirmButtonText: $t('Common.Confirm'),
        cancelButtonText: $t('Common.Cancel'),
        type: 'warning'
      }
    )

    permissions.value = JSON.parse(JSON.stringify(originalPermissions.value))
    grantedPermissions.value = originalPermissions.value
      .filter(p => p.isGranted)
      .map(p => p.name)

    ElMessage.success($t('PermissionManagement.ResetToDefaultSuccess'))
  } catch (error) {
    // 用户取消
  }
}

// 处理提交
const handleSubmit = async () => {
  if (!props.entityId || !props.entityType) return

  try {
    loading.value = true

    const updateRequest = {
      permissions: permissions.value.map(p => ({
        name: p.name,
        isGranted: p.isGranted
      }))
    }

    let result
    switch (props.entityType) {
      case 'user':
        result = await permissionService.updateUserPermissions(props.entityId, updateRequest)
        break
      case 'role':
        result = await permissionService.updateRolePermissions(props.entityId, updateRequest)
        break
      case 'tenant':
        result = await permissionService.updateTenantPermissions(props.entityId, updateRequest)
        break
      default:
        throw new Error('不支持的实体类型')
    }

    ElMessage.success($t('PermissionManagement.UpdatePermissionsSuccess'))
    emit('success')
    handleClose()
  } catch (error) {
    console.error('更新权限失败:', error)
    ElMessage.error($t('PermissionManagement.UpdatePermissionsFailed'))
  } finally {
    loading.value = false
  }
}

// 处理关闭
const handleClose = () => {
  if (loading.value) return

  dialogVisible.value = false
  setTimeout(() => {
    searchKeyword.value = ''
    selectedGroup.value = ''
    filterType.value = 'all'
    expandedKeys.value = []
    selectedPermissions.value = []
    permissions.value = []
    originalPermissions.value = []
    grantedPermissions.value = []
  }, 300)
}

// 监听对话框打开
watch(() => props.modelValue, (newValue) => {
  if (newValue && props.entityId && props.entityType) {
    loadPermissions()
  }
})
</script>

<style scoped>
.permission-dialog {
  height: 600px;
  display: flex;
  flex-direction: column;
}

.permission-header {
  margin-bottom: 20px;
}

.search-row {
  align-items: center;
}

.permission-tree-container {
  flex: 1;
  overflow: hidden;
  border: 1px solid #dcdfe6;
  border-radius: 4px;
  padding: 10px;
}

.permission-node {
  display: flex;
  justify-content: space-between;
  align-items: center;
  width: 100%;
  padding: 8px 0;
}

.permission-info {
  flex: 1;
}

.permission-name {
  font-weight: 500;
  color: #303133;
  display: flex;
  align-items: center;
  gap: 8px;
}

.permission-description {
  font-size: 12px;
  color: #909399;
  margin-top: 4px;
}

.permission-meta {
  display: flex;
  gap: 12px;
  margin-top: 4px;
}

.permission-group,
.permission-parent {
  font-size: 11px;
  color: #c0c4cc;
  background-color: #f5f7fa;
  padding: 2px 6px;
  border-radius: 2px;
}

.permission-actions {
  margin-left: 16px;
}

.permission-stats {
  margin: 20px 0;
  padding: 16px;
  background-color: #f8f9fa;
  border-radius: 4px;
}

.stat-percentage {
  font-size: 12px;
  color: #909399;
  margin-left: 4px;
}

.permission-bulk-actions {
  padding: 16px;
  border-top: 1px solid #ebeef5;
  background-color: #fafafa;
  border-radius: 0 0 4px 4px;
}

.dialog-footer {
  text-align: right;
}

:deep(.el-tree) {
  height: 100%;
  overflow-y: auto;
}

:deep(.el-tree-node__content) {
  height: auto;
  padding: 4px 0;
}

:deep(.el-statistic__head) {
  font-size: 12px;
  color: #909399;
}

:deep(.el-statistic__content) {
  font-size: 20px;
  font-weight: 600;
}
</style>